<!--
 * @Description: 
 * @Author: Xiaochuan-W
 * @Date: 2023-09-26 09:42:44
 * @LastEditors: Xiaochuan-W
 * @LastEditTime: 2023-10-13 10:00:43
-->
<template>
	<XConfigProvider>

		<el-tree
			ref="refTree"
			:data="treeData"
			check-strictly
			element-loading-text="拼命加载中"
			:node-key="treeProps.value || 'id'"
			:props="cloneTreeProps"
			:lazy="lazy"
			:load="load"
			:render-after-expand="false"
			:expand-on-click-node="false"
			:default-expand-all="!lazy"
			:show-checkbox="showCheckbox"
			:default-checked-keys="modelValue"
			highlight-current
			@check-change="handleMenuCheckChange"
			@check="handleMenuChange"
			@node-click="
				(node:Record<string,any>) => {
					emit('node-click', node);
				}
			"
		/>
	</XConfigProvider>
</template>

<script lang="ts" setup>
import XConfigProvider from '../XConfigProvider/index.vue'
import {ref,reactive} from 'vue'
import {ElTree} from 'element-plus'

const emit = defineEmits(['node-click', 'update:modelValue']);

const props = defineProps({
	modelValue: {
		type: Array as any,
		default() {
			return [];
		}
	},
	treeData: {
		type: Array,
		default() {
			return [];
		}
	},
	treeProps: {
		type: Object,
		default: () => ({})
	},
	lazy: {
		type: Boolean,
		default: () => true
	},
	load: {
		type: Function as any,
		default: () => () => {}
	},
	showCheckbox: {
		type: Boolean,
		default: () => false
	}
});

const defaultTreeProps = {
	label: 'name',
	value: 'id', // 新增
	parentId: 'parentId', // 新增
	children: 'children',
	disabled: 'disabled',
	isLeaf: 'isLeaf',
	class: 'class'
} as any;
const cloneTreeProps = reactive(
	Object.assign(defaultTreeProps, props.treeProps)
);

const refTree = ref<any>(null);

// 树节点选择监听
const handleMenuCheckChange = (data: any, check: boolean) => {
	if (check) {
		// 节点选中时同步选中父节点
		const parentId = data[cloneTreeProps.parentId];
		refTree.value.setChecked(parentId, true, false);
	} else {
		// 节点取消选中时同步取消选中子节点
		data[cloneTreeProps.children] != null &&
			data[cloneTreeProps.children].forEach((element: any) => {
				refTree.value.setChecked(element[cloneTreeProps.value], false, false);
			});
	}
};
const handleMenuChange = (data: any, check: any) => {
	if (
		data[cloneTreeProps.children]?.length &&
		check.checkedKeys.includes(data[cloneTreeProps.value])
	) {
		setCheckedOfDeep(data, cloneTreeProps.value, true);
	}
	emit('update:modelValue', refTree.value.getCheckedKeys());
};
// 递归选中子节点
const setCheckedOfDeep = (data: any, nodeKey = 'id', val = true) => {
	refTree.value.setChecked(data[nodeKey], val, true);
	return (
		data[cloneTreeProps.children]?.length &&
		data[cloneTreeProps.children].map((item: any) =>
			setCheckedOfDeep(item, nodeKey, val)
		)
	);
};
defineExpose({ refTree });
</script>
<style scoped></style>
